#include <stdlib.h>
#include <Carbon/Carbon.h>

#include "KeyCapture.h"

char msg[1024] = {0};
AXUIElementRef frontMostApp;

void trace(char *msg)
{
    FILE *file = fopen("/Users/macos2/Desktop/ax.txt", "a");
    fprintf(file, msg);
    fclose(file);
}

bool amIAuthorized()
{
    if (AXAPIEnabled())
    {
        return true;
    }

    if (AXIsProcessTrusted())
    {
        return true;
    }

    trace("AX API is not enabled or Process not trusted.\n");
    return false;
}

void makeProcessTrusted()
{
    if (AXMakeProcessTrusted(CFSTR("/usr/bin/accessability")) != kAXErrorSuccess)
    {
        trace("Could not make process trusted.\n");
    }
    trace("Make process trusted successfully.\n");
}

AXUIElementRef getFrontMostApp()
{
    pid_t pid;
    ProcessSerialNumber psn;

    GetFrontProcess(&psn);
    GetProcessPID(&psn, &pid);
    return AXUIElementCreateApplication(pid);
}

int main(int argc, char** argv)
{
    KeyCapture* pKeyCapture = new KeyCapture();
//    pKeyCapture->m_runLoop = CFRunLoopGetCurrent();

    EventTypeSpec spec = { kEventClassApplication,  kEventAppFrontSwitched };
	if (InstallApplicationEventHandler(NewEventHandlerUPP(&pKeyCapture->AppFrontSwitchedHandler),
            1, &spec, pKeyCapture, NULL) != noErr)
	{
        printf("InstallApplicationEventHandler failed\n");
	}

    int i;
    AXError err;
    AXValueRef temp;
    CGSize windowSize;
    CGPoint windowPosition;

    AXUIElementRef frontMostUIElement;

    for (i = 0; i < 2; i++) {
        sleep(1);
        printf("%d", i + 1);
        if (i < 4) {
            printf("...");
            fflush(stdout);
        } else {
            printf("\n");
        }
    }

    CFRunLoopSourceContext context = { 0, NULL };
	CFRunLoopSourceRef runLoopSource = CFRunLoopSourceCreate(NULL, 0, &context);

	CFRunLoopAddSource(CFRunLoopGetCurrent(), runLoopSource, kCFRunLoopDefaultMode);
	CFRelease(runLoopSource);
	CFRunLoopRun();

//    frontMostApp = getFrontMostApp();
//
//    err = AXUIElementCopyAttributeValue(frontMostApp, kAXFocusedWindowAttribute, (CFTypeRef *)&frontMostWindow);
//    if (err != kAXErrorSuccess)
//    {
//		printf("AXUIElementCopyAttributeValue with kAXFocusedWindowAttribute failed [%d]", err);
//		CFRelease(frontMostApp);
//		return 1;
//	}
//
//    err = AXUIElementCopyAttributeValue(frontMostWindow, kAXTitleAttribute, (CFTypeRef *)&windowTitle);
//    if (err != kAXErrorSuccess)
//    {
//		printf("AXUIElementCopyAttributeValue with kAXTitleAttribute failed [%d]", err);
//		CFRelease(frontMostApp);
//		return 2;
//	}
//    CFShow(windowTitle);
//    char title[512] = {0};
//    CFStringGetCString(windowTitle, title, 512, kCFStringEncodingUTF8);
//    printf("window title: %s\n", title);

    
//	AXUIElementRef systemWide = AXUIElementCreateSystemWide();
//	if (NULL == systemWide)
//    {
//		printf("AXUIElementCreateApplication failed\n");
//		return 1;
//	}
//
//	AXError err;
//    AXUIElementRef frontMostApp = NULL;
//
//    err = AXUIElementCopyAttributeValue(systemWide, (CFStringRef)kAXFocusedApplicationAttribute, (CFTypeRef*)&frontMostApp);
//	if (err != kAXErrorSuccess) {
//		printf("AXUIElementCopyAttributeValue with kAXFocusedApplicationAttribute failed [%d]\n", err);
//		CFRelease(systemWide);
//		return 1;
//	}
//
//    AXUIElementRef focusedWindow = NULL;
//    err = AXUIElementCopyAttributeValue(frontMostApp, (CFStringRef)kAXFocusedWindowAttribute, (CFTypeRef*)&focusedWindow);
//	if (err != kAXErrorSuccess) {
//		M_ERROR(L"AXUIElementCopyAttributeValue with kAXFocusedWindowAttribute failed [%d]", err);
//		CFRelease(frontMostApp);
//		StartCompositionIndex = currentSelectTextRange.location;
//		return false;
//	}
//    
//    err = AXUIElementCopyAttributeValue(frontMostApp, kAXFocusedUIElementAttribute, (CFTypeRef*)&focusedUIElement);
//	if (err != kAXErrorSuccess) {
//		M_ERROR(L"AXUIElementCopyAttributeValue with kAXFocusedUIElementAttribute failed [%d]", err);
//		CFRelease(frontMostApp);
//		StartCompositionIndex = currentSelectTextRange.location;
//		return false;
//	}

    printf("Finished\n");
    return (EXIT_SUCCESS);
}

